﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.Serialization.Formatters.Binary;
using System.Text;
using System.Threading.Tasks;
using System.Xml;
using System.Xml.Serialization;

namespace YouDaoNotesCodes.XML
{
    class XMLSerializationandDeserialization
    {
        #region XmlSerializer 常用
        /// <summary>
        /// XmlSerializer常用
        /// </summary>
        public void XmlSerializerType()
        {
            //序列化
            Person person = new Person();
            person.age = 18;
            person.name = "tom";
            person.secret = "i will not tell you";
            FileStream stream = new FileStream(@"c:\temp\xmlFormat.xml", FileMode.Create);//存放序列化文件

            XmlSerializer xmlserilize = new XmlSerializer(typeof(Person));
            xmlserilize.Serialize(stream, person);
            stream.Close();

            //反序列化
            //Person person1 = new Person();
            FileStream stream1 = new FileStream(@"c:\temp\xmlFormat.xml", FileMode.Open);

            //XmlSerializer xmlserilize = new XmlSerializer(typeof(person));
            person = (Person)xmlserilize.Deserialize(stream1);
            stream.Close();

            Console.WriteLine(person.age + person.name + person.secret);
        }
        #endregion

        #region BinaryFormatter性能好
        /// <summary>
        /// BinaryFormatter性能好
        /// </summary>
        public void BinaryFormatterType()
        {
            //序列化
            Person person = new Person();
            person.age = 18;
            person.name = "tom";
            person.secret = "i will not tell you";
            FileStream stream = new FileStream(@"c:\temp\person.dat", FileMode.Create);

            BinaryFormatter bFormat = new BinaryFormatter();
            bFormat.Serialize(stream, person);
            stream.Close();

            //反序列化
            //Person person = new Person();
            FileStream stream1 = new FileStream(@"c:\temp\person.dat", FileMode.Open);

            //BinaryFormatter bFormat = new BinaryFormatter();
            person = (Person)bFormat.Deserialize(stream1);//反序列化得到的是一个object对象.必须做下类型转换
            stream.Close();
            Console.WriteLine(person.age + person.name + person.secret);//结果为18tom.因为secret没有有被序列化.

        }
        #endregion

        /// <summary>
        /// 序列化object对象为XML字符串
        /// </summary>
        /// <param name="obj">实体类或List集合类</param>
        /// <returns></returns>
        public static string Serialize(object obj)
        {
            return Serialize(obj, false, true);
        }
        /// <summary>
        /// 序列化object对象为XML字符串
        /// </summary>
        /// <param name="obj">实体类或List集合类</param>
        /// <param name="isOmitXmlDeclaration"><![CDATA[是否去除Xml声明<?xml version="1.0" encoding="utf-8"?>]]></param>
        /// <param name="isIndent">是否缩进显示</param>
        /// <returns></returns>
        public static string Serialize(object obj, bool isOmitXmlDeclaration, bool isIndent)
        {
            try
            {
                string xmlString;
                XmlWriterSettings xmlWriterSettings = new XmlWriterSettings();

                //去除xml声明
                //<?xml version="1.0" encoding="utf-8"?>
                xmlWriterSettings.OmitXmlDeclaration = isOmitXmlDeclaration;
                //不换行不缩进
                xmlWriterSettings.Indent = isIndent;
                //默认为UTF8编码
                xmlWriterSettings.Encoding = Encoding.UTF8;

                using (MemoryStream memoryStream = new MemoryStream())
                {
                    using (XmlWriter xmlWriter = XmlWriter.Create(memoryStream, xmlWriterSettings))
                    {
                        //去除默认命名空间xmlns:xsd和xmlns:xsi
                        XmlSerializerNamespaces ns = new XmlSerializerNamespaces();
                        ns.Add("", "");

                        //序列化对象
                        XmlSerializer xmlSerializer = new XmlSerializer(obj.GetType());
                        xmlSerializer.Serialize(xmlWriter, obj, ns);
                    }
                    xmlString = Encoding.UTF8.GetString(memoryStream.ToArray());
                }
                return xmlString.TrimStart('?');
            }
            catch (Exception)
            {
                return null;
            }
        }

        /////////////////////////////////////////////////////////////////
        ///// <summary>
        ///// XMLHelper
        ///// </summary>
        ///// <param name="model"></param>
        ///// <returns></returns>
        //public static string Serialize<T>(T model) where T : class
        //{
        //    string xml;
        //    using (var ms = new MemoryStream())
        //    {
        //        XmlSerializer xmlSer = new XmlSerializer(typeof(T));
        //        xmlSer.Serialize(ms, model);
        //        ms.Position = 0;
        //        StreamReader sr = new StreamReader(ms);
        //        xml = sr.ReadToEnd();
        //    }
        //    return xml;
        //}

        ///// <summary>
        ///// 反序列化
        ///// </summary>
        ///// <typeparam name="T">实体</typeparam>
        ///// <param name="strXml">xml文件</param>
        ///// <returns></returns>
        //public static T Deserialize<T>(string strXml) where T : class
        //{
        //    try
        //    {
        //        object obj;
        //        using (MemoryStream memoryStream = new MemoryStream(Encoding.UTF8.GetBytes(strXml)))
        //        {
        //            using (XmlReader xmlReader = XmlReader.Create(memoryStream))
        //            {
        //                XmlSerializer xmlSerializer = new XmlSerializer(typeof(T));
        //                obj = xmlSerializer.Deserialize(xmlReader);
        //            }
        //        }
        //        return obj as T;
        //    }
        //    catch (Exception)
        //    {
        //        return null;
        //    }
        //}

        ///// <summary>
        ///// 反序列化
        ///// </summary>
        ///// <typeparam name="T">实体</typeparam>
        ///// <param name="stream">流文件</param>
        ///// <returns></returns>
        //public static T Deserialize<T>(Stream stream) where T : class
        //{
        //    try
        //    {
        //        object obj;
        //        XmlSerializer xmldes = new XmlSerializer(typeof(T));
        //        obj = xmldes.Deserialize(stream);

        //        return obj as T;
        //    }
        //    catch (Exception)
        //    {
        //        return null;
        //    }
        //}
    }

    [Serializable] //如果要想保存某个class中的字段,必须在class前面加个这样attribute(C#里面用中括号括起来的标志符)
    public class Person
    {
        public int age;

        public string name;

        [NonSerialized] //如果某个字段不想被保存,则加个这样的标志

        public string secret;

    }
}
